package com.lucien.Stack;

import java.util.Scanner;

/**
 * 单链表模拟栈
 */

public class LinkedStackDemo {
    public static void main(String[] args) {
        LinkedStack stack = new LinkedStack(4);
        Scanner scanner = new Scanner(System.in);
        String key = "";
        boolean loop = true;
        while (loop) {
            System.out.println("show:显示");
            System.out.println("exit:退出");
            System.out.println("push:入栈");
            System.out.println("pop:出栈");
            System.out.println("请输入你的选择：");
            key = scanner.next();
            switch (key) {
                case "show":
                    stack.list();
                    break;
                case "exit":
                    scanner.close();
                    loop = false;
                    break;
                case "push":
                    System.out.println("请输入数据：");
                    String data = scanner.next();
                    stack.push(data);
                    break;
                case "pop":
                    stack.pop();
                    break;

                default:
                    break;
            }
        }
        System.out.println("程序退出！");
    }
}
class LinkedStack{
    private int maxsize;//栈的大小
    private singleList stack;//单链表
    private int top = -1;//栈顶

    public LinkedStack(int maxsize){
        this.maxsize = maxsize;
        stack = new singleList();
        stack.creatLinked(this.maxsize);
    }

    //栈满
    public boolean isFull(){
        return top == maxsize - 1;
    }

    //栈空
    public boolean isEmpty(){
        return top == -1;
    }

    //入栈
    public void push(String data){
        if (isFull()){
            System.out.println("栈满");
            return;
        }
        top++;
        stack.add(top,data);
    }

    //出栈
    public void pop(){
        if (isEmpty()){
            System.out.println("栈空");
            return;
        }
        System.out.printf("stack[%d]的值是%d", top, stack.getData(top));
        top--;
    }

    // 遍历
    public void list() {
        if (isEmpty()) {
            System.out.println("栈空，无法遍历！");
        }
        stack.list(top);
    }

    // 正常遍历,检测链表使用
    public void list2() {
        stack.list2();
    }
}
class singleList{
    private Student head = new Student(-1);

    //创建单链表
    public void creatLinked(int maxsize){
        if (maxsize < 1){
            System.out.println("输入的参数不符合，请重新输入");
            return;
        }
        Student temp = head;
        for (int i = 0; i < maxsize; i++) {
            Student student = new Student(i);
            temp.setNext(student);
            temp = student;
        }
    }

    //根据栈顶的指针 将数据存入到链表
    public void add(int top,String data){
        Student temp = head;
        //将指针移动到栈顶
        for (int i = 0; i < top; i++) {
            temp=temp.getNext();
        }
        //将数据存放到下一个节点
        temp.getNext().setData(data);
    }

    //根据栈顶的指针将链表的数据取下来，不是删除节点
    public String getData(int top){
        Student temp = head;
        //将指针移动到栈顶
        for (int i = 0; i < top+1; i++) {
            temp=temp.getNext();
        }
        //取出数据
        String data = temp.getData();
        return data;
    }

    //遍历链表(逆序)
    public void list(int top){
        Student temp = head;
        while (top >= 0){
            //将指针移动到栈顶
            for (int i = 0; i < top+1; i++) {
                temp=temp.getNext();
            }
            System.out.println("stack["+top+"]:"+temp.getData()+"-");
            //栈顶往下移动一次
            top--;
            //指针还原到头节点
            temp = head;
        }
    }

    //正常遍历链表
    public void list2(){
        Student temp = head;
        while (true){
            if (temp == null){
            break;
            }
            System.out.println(temp);
            temp = temp.getNext();
        }
    }
}
class Student{
    public int no;
    public String data;
    public Student next;

    public Student(int no){
        this.no=no;
    }
    public int getNo() {
        return no;
    }

    public void setNo(int no) {
        this.no = no;
    }

    public String getData() {
        return data;
    }

    public void setData(String data) {
        this.data = data;
    }

    public Student getNext() {
        return next;
    }

    public void setNext(Student next) {
        this.next = next;
    }

    @Override
    public String toString() {
        return "test{" +
                "no=" + no +
                ", data='" + data + '\'' +
                ", next=" + next +
                '}';
    }
}
